package org.xxpay.manage.config.ctrl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import org.xxpay.core.common.annotation.MethodLog;
import org.xxpay.core.common.constant.Constant;
import org.xxpay.core.common.constant.RetEnum;
import org.xxpay.core.common.domain.BizResponse;
import org.xxpay.core.common.domain.XxPayPageRes;
import org.xxpay.core.common.domain.XxPayResponse;
import org.xxpay.core.entity.*;
import org.xxpay.manage.common.ctrl.BaseController;
import org.xxpay.manage.common.service.RpcCommonService;
import org.xxpay.manage.config.service.CommonConfigService;
import org.xxpay.manage.utils.PayOrderDTO;

import javax.servlet.http.HttpServletRequest;
import java.math.BigDecimal;
import java.util.*;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * @author: dingzhiwei
 * @date: 18/05/04
 * @description: 支付通道
 */
@RestController
@RequestMapping(Constant.MGR_CONTROLLER_ROOT_PATH + "/config/pay_passage")
public class PayPassageController extends BaseController {

    @Autowired
    private RpcCommonService rpcCommonService;

    @Autowired
    private CommonConfigService commonConfigService;

    @RequestMapping("/list")
    @ResponseBody
    public ResponseEntity<?> list(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        PayPassage payPassage = getObject(param, PayPassage.class);
        int count = rpcCommonService.rpcPayPassageService.count(payPassage);
        if(count == 0) return ResponseEntity.ok(XxPayPageRes.buildSuccess());//获取数据成功,支付通道获取成功
        List<PayPassage> payPassageList = rpcCommonService.rpcPayPassageService.select((getPageIndex(param) -1) * getPageSize(param), getPageSize(param), payPassage);
        // 支付接口类型Map
        Map payInterfaceTypeMap = commonConfigService.getPayInterfaceTypeMap();
        // 支付接口Map
        Map payInterfaceMap = commonConfigService.getPayInterfaceMap();
        // 支付类型Map
        Map payTypeMap = commonConfigService.getPayTypeMap();

        // 转换前端显示
        List<JSONObject> objects = new LinkedList<>();
        for(PayPassage info : payPassageList) {
            JSONObject object = (JSONObject) JSON.toJSON(info);
            object.put("payTypeName", payTypeMap.get(info.getPayType()));               // 转换支付类型名称
            object.put("ifTypeName", payInterfaceTypeMap.get(info.getIfTypeCode()));    // 转换接口类型名称
            object.put("ifName", payInterfaceMap.get(info.getIfCode()));                // 转换支付接口名称
            objects.add(object);
        }
        return ResponseEntity.ok(XxPayPageRes.buildSuccess(objects, count));
    }

    @RequestMapping("/get")
    @ResponseBody
    public ResponseEntity<?> get(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        Integer id = getIntegerRequired(param, "id");
        PayPassage payPassage = rpcCommonService.rpcPayPassageService.findById(id);
        return ResponseEntity.ok(XxPayResponse.buildSuccess(payPassage));
    }

    @RequestMapping("/update")
    @ResponseBody
    @MethodLog( remark = "修改支付通道" )
    public ResponseEntity<?> update(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        PayPassage payPassage = getObject(param, PayPassage.class);
        String ifCode = payPassage.getIfCode();
        PayInterface payInterface = rpcCommonService.rpcPayInterfaceService.findByCode(ifCode);
        if(payInterface == null) {
            return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_MGR_PAY_INTERFACE_NOT_EXIST));
        }
        payPassage.setIfTypeCode(payInterface.getIfTypeCode()); // 设置支付接口类型

        int count = rpcCommonService.rpcPayPassageService.update(payPassage);
        if(count == 1) return ResponseEntity.ok(BizResponse.buildSuccess());
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }

//    @RequestMapping("/updateList")
//    @ResponseBody
//    @MethodLog( remark = "多选修改支付通道启用或停用" )
//    public ResponseEntity<?> updateList(HttpServletRequest request) {
//        JSONObject param = getJsonParam(request);
//        String orderIdsParam = getStringRequired(param, "payPassageList");
//        List<PayPassage> payPassages = JSON.parseArray(orderIdsParam, PayPassage.class);
//        AtomicInteger count= new AtomicInteger();
//        payPassages.stream().filter(e->e.getId()!=null).forEach(e->{
//            PayPassage payPassage = new PayPassage();
//            payPassage.setId(e.getId());
//            payPassage.setStatus(e.getStatus());
//            count.set(rpcCommonService.rpcPayPassageService.update(payPassage));
//        });
//        if(count.get() >=1) return ResponseEntity.ok(BizResponse.buildSuccess());
//        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
//    }
    @RequestMapping("/updateList")
    @ResponseBody
    @MethodLog(remark = "多选修改支付通道启用或停用")
    public ResponseEntity<?> updateList(@RequestBody List<Integer> payPassageList, @RequestParam Byte status) {
        AtomicInteger count = new AtomicInteger();
        payPassageList.forEach(payPassageId -> {
            PayPassage payPassage = new PayPassage();
            payPassage.setId(payPassageId);
            payPassage.setStatus(status);
            count.set(rpcCommonService.rpcPayPassageService.update(payPassage));
        });
        if (count.get() >= 1) {
            return ResponseEntity.ok(BizResponse.buildSuccess());
        }
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }

    @RequestMapping("/prohibitList")
    @ResponseBody
    @MethodLog(remark = "多选修改支付通道启用或停用")
    public ResponseEntity<?> prohibitList(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        String payPassagesStr = param.getString("payPassageList");
        JSONArray payPassages = new JSONArray();
        if (payPassagesStr != null && !payPassagesStr.isEmpty()) {
            String[] ids = payPassagesStr.split(",");
            for (String id : ids) {
                payPassages.add(Integer.parseInt(id));
            }
        }
        AtomicInteger count = new AtomicInteger();
        payPassages.stream().filter(Objects::nonNull).forEach(e -> {
            int payPassageId = (int) e;
            PayPassage payPassage = new PayPassage();
            payPassage.setId(payPassageId);
            payPassage.setStatus((byte) 0);
            count.set(rpcCommonService.rpcPayPassageService.update(payPassage));
        });
        if (count.get() >= 1) {
            return ResponseEntity.ok(BizResponse.buildSuccess());
        }
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }
    @RequestMapping("/startList")
    @ResponseBody
    @MethodLog(remark = "多选修改支付通道启用或停用")
    public ResponseEntity<?> startList(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        String payPassagesStr = param.getString("payPassageList");
        JSONArray payPassages = new JSONArray();
        if (payPassagesStr != null && !payPassagesStr.isEmpty()) {
            String[] ids = payPassagesStr.split(",");
            for (String id : ids) {
                payPassages.add(Integer.parseInt(id));
            }
        }
        AtomicInteger count = new AtomicInteger();
        payPassages.stream().filter(Objects::nonNull).forEach(e -> {
            int payPassageId = (int) e;
            PayPassage payPassage = new PayPassage();
            payPassage.setId(payPassageId);
            payPassage.setStatus((byte) 1);
            count.set(rpcCommonService.rpcPayPassageService.update(payPassage));
        });
        if (count.get() >= 1) {
            return ResponseEntity.ok(BizResponse.buildSuccess());
        }
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }
//    @RequestMapping("/startList")
//    @ResponseBody
//    @MethodLog(remark = "多选修改支付通道启用或停用")
//    public ResponseEntity<?> startList(HttpServletRequest request) {
//        JSONObject param = getJsonParam(request);
//        String orderIdsParam = getStringRequired(param, "payPassageList");
//        List<Integer> payPassages = JSON.parseArray(orderIdsParam, Integer.class);
//        AtomicInteger count= new AtomicInteger();
//        payPassages.stream().filter(Objects::nonNull).forEach(e->{
//            PayPassage payPassage = new PayPassage();
//            payPassage.setId(e);
//            payPassage.setStatus((byte) 1);
//            count.set(rpcCommonService.rpcPayPassageService.update(payPassage));
//        });
//        if (count.get() >= 1) {
//            return ResponseEntity.ok(BizResponse.buildSuccess());
//        }
//        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
//
//    }

    @RequestMapping("/deleteList")
    @ResponseBody
    @MethodLog( remark = "多选删除支付通道" )
    public ResponseEntity<?> deleteList(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        String payPassagesStr = param.getString("payPassageList");
        JSONArray payPassages = new JSONArray();
        if (payPassagesStr != null && !payPassagesStr.isEmpty()) {
            String[] ids = payPassagesStr.split(",");
            for (String id : ids) {
                payPassages.add(Integer.parseInt(id));
            }
        }
        AtomicInteger count= new AtomicInteger();
        payPassages.stream().filter(Objects::nonNull).forEach(e->{
            PayPassage payPassage = new PayPassage();
            payPassage.setId((Integer) e);
            count.set(rpcCommonService.rpcPayPassageService.delete(payPassage));
        });
        if(count.get() >=1) return ResponseEntity.ok(BizResponse.buildSuccess());
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }

    @RequestMapping("/risk_update")
    @ResponseBody
    @MethodLog( remark = "修改支付通道风控" )
    public ResponseEntity<?> updateRisk(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        PayPassage payPassage = getObject(param, PayPassage.class);
        Long maxDayAmount = payPassage.getMaxDayAmount();
        Long maxEveryAmount = payPassage.getMaxEveryAmount();
        Long minEveryAmount = payPassage.getMinEveryAmount();
        // 元转分
        if(maxDayAmount != null) payPassage.setMaxDayAmount(maxDayAmount * 100);
        if(maxEveryAmount != null) payPassage.setMaxEveryAmount(maxEveryAmount * 100);
        if(minEveryAmount != null) payPassage.setMinEveryAmount(minEveryAmount * 100);
        int count = rpcCommonService.rpcPayPassageService.update(payPassage);
        if(count == 1) return ResponseEntity.ok(BizResponse.buildSuccess());
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }

    @RequestMapping("/rate_update")
    @ResponseBody
    @MethodLog( remark = "修改支付通道费率" )
    public ResponseEntity<?> updateRate(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        Integer id = getIntegerRequired(param, "id");
        String passageRate = getStringRequired(param, "passageRate");
        PayPassage payPassage = new PayPassage();
        payPassage.setId(id);
        payPassage.setPassageRate(new BigDecimal(passageRate));
        int count = rpcCommonService.rpcPayPassageService.updateRate(payPassage);
        if(count == 1) return ResponseEntity.ok(BizResponse.buildSuccess());
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }

    @RequestMapping("/add")
    @ResponseBody
    @MethodLog( remark = "新增支付通道" )
    public ResponseEntity<?> add(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        PayPassage payPassage = getObject(param, PayPassage.class);
        String ifCode = payPassage.getIfCode();
        PayInterface payInterface = rpcCommonService.rpcPayInterfaceService.findByCode(ifCode);
        if(payInterface == null) {
            ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_MGR_PAY_INTERFACE_NOT_EXIST));
        }
        payPassage.setIfTypeCode(payInterface.getIfTypeCode()); // 设置支付接口类型
        int count = rpcCommonService.rpcPayPassageService.add(payPassage);
        if(count == 1) return ResponseEntity.ok(BizResponse.buildSuccess());
        return ResponseEntity.ok(BizResponse.build(RetEnum.RET_COMM_OPERATION_FAIL));
    }

    /**
     * 根据支付通道ID,获取支付账号配置定义描述
     * @param request
     * @return
     */
    @RequestMapping("/pay_config_get")
    @ResponseBody
    public ResponseEntity<?> getPayConfig(HttpServletRequest request) {
        JSONObject param = getJsonParam(request);
        Integer payPassageId = getIntegerRequired(param, "payPassageId");
        PayPassage payPassage = rpcCommonService.rpcPayPassageService.findById(payPassageId);
        if(payPassage == null) {
            return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_RECORD_NOT_EXIST));
        }
        String ifCode = payPassage.getIfCode();
        String ifTypeCode = payPassage.getIfTypeCode();

        // 如果接口配置了定义描述,则使用接口
        PayInterface payInterface = rpcCommonService.rpcPayInterfaceService.findByCode(ifCode);
        if(payInterface != null && StringUtils.isNotBlank(payInterface.getParam())) {
            // 支付接口类型Map
            Map payInterfaceTypeMap = commonConfigService.getPayInterfaceTypeMap();
            JSONObject object = (JSONObject) JSON.toJSON(payInterface);
            object.put("ifTypeName", payInterfaceTypeMap.get(payInterface.getIfTypeCode()));
            return ResponseEntity.ok(XxPayResponse.buildSuccess(object));
        }
        // 使用接口类型配置的定义描述
        PayInterfaceType payInterfaceType = rpcCommonService.rpcPayInterfaceTypeService.findByCode(ifTypeCode);
        if(payInterfaceType != null && StringUtils.isNotBlank(payInterfaceType.getParam())) {
            // 支付接口类型Map
            Map payInterfaceTypeMap = commonConfigService.getPayInterfaceTypeMap();
            JSONObject object = (JSONObject) JSON.toJSON(payInterfaceType);
            object.put("ifTypeName", payInterfaceTypeMap.get(payInterfaceType.getIfTypeCode()));
            return ResponseEntity.ok(XxPayResponse.buildSuccess(object));
        }
        return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_RECORD_NOT_EXIST));
    }

    /**
     * 还未支付的订单,发起的订单请求的测试接口
     * @return
     */
    @RequestMapping("/test")
    @ResponseBody
    public ResponseEntity<?> test(HttpServletRequest request) {

        JSONObject param = getJsonParam(request);
        PayOrderDTO payload = getObject(param,PayOrderDTO.class);
        final Long amount = payload.getAmount();
        final String ifCode = payload.getIfCode();
        //获取商户id和对应的appkey以及支付路径(密钥,支付接口添加中的商户密钥,但是数据库中叫appkey)
        String ifTypeMchId ;
        String ifTypeAppKey;
        String ifTypeReqUrl;
        PayInterface payInterface = rpcCommonService.rpcPayInterfaceService.findByCode(ifCode);
        Optional<PayInterface> optional =Optional.ofNullable(payInterface);
        if (optional.isPresent()) {
            final String ifTypeCode = payInterface.getIfTypeCode();
            final PayInterfaceType byCode = rpcCommonService.rpcPayInterfaceTypeService.findByCode(ifTypeCode);
            Optional<PayInterfaceType> byCodeOfnull =Optional.ofNullable(byCode);
            if (byCodeOfnull.isPresent()) {
                ifTypeMchId = byCode.getIfTypeMchId();
                if (ifTypeMchId == null) {
                    return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_OPERATION_FAIL, "支付接口类型所绑商户id为不能空"));
                }
                ifTypeAppKey = byCode.getIfTypeAppKey();
                ifTypeReqUrl = byCode.getIfTypeReqUrl();
                if (ifTypeAppKey == null) {
                    return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_OPERATION_FAIL, "支付接口类型所绑appkey为空"));
                }
//                MchPayPassage mchPayPassage = rpcCommonService.rpcMchPayPassageService.findByMchIdAndProductId(Long.valueOf(ifTypeMchId), 8000);
//                if(mchPayPassage == null) {
//                    System.out.println(mchPayPassage);
//                }
            }else {
                return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_RECORD_NOT_EXIST,"支付接口类型不存在"));
            }
        }else return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_RECORD_NOT_EXIST,"支付接口不存在"));
        final PayOrder payOrder =
                rpcCommonService.rpcPayInterfaceService
                        .payInterface2Order(payInterface, amount,Long.valueOf(ifTypeMchId));
        //获取支付产品,本来逻辑上是要这样写的,但是好像只支持8000,8001会报错
//        final String payType = payInterface.getPayType();
//        final List<PayProduct> payProducts = rpcCommonService.rpcPayProductService.selectAllByPayType(payType);
//        if (payProducts.size() == 0) {
//            return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_OPERATION_FAIL, "支付接口和商户id对应产品不存在"));
//        }
//        payOrder.setProductId(payProducts.get(0).getId());
        final String ifName = payInterface.getIfName();
        final Integer productId = rpcCommonService.rpcPayInterfaceService.findByName(ifName);
        payOrder.setProductId(productId);//文档里面写的是8000支付宝,8001微信


        final String signature = rpcCommonService.rpcPayInterfaceService.generateSign(payOrder, ifTypeAppKey);
        final String back = rpcCommonService.rpcPayInterfaceService.sendToPay(payOrder, signature ,ifTypeReqUrl);
        if (back.contains("SUCCESS")){
//            JSON.parseObject(back, payOrder.getClass());
            return ResponseEntity.ok(XxPayResponse.buildSuccess(back));
        }else return ResponseEntity.ok(XxPayResponse.build(RetEnum.RET_COMM_OPERATION_FAIL,back));

    }
    @RequestMapping("/test2")
    @ResponseBody
    public ResponseEntity<?> test2(HttpServletRequest request) {
        return ResponseEntity.ok(XxPayResponse.buildSuccess("签名成功"));
    }
    @RequestMapping("/isSign")
    @ResponseBody
    public ResponseEntity<?> isSign(@RequestParam Boolean isSign) {
        if (isSign) {
            return ResponseEntity.ok(XxPayResponse.buildSuccess("签名成功"));
        }
        return ResponseEntity.ok(XxPayResponse.buildSuccess("签名错误"));


    }

}
